﻿using System;
using UnityEditor;
using UnityEngine;
using UnityEngine.UIElements;
using winS.UnityEditor.UIElement;
using winS.UnityEditor.Undo;
using Button = winS.UnityEditor.UIElement.Button;
using Object = UnityEngine.Object;

namespace winS.UnityEditor.GUI
{
    public class GUIFactory : ElementFactory
    {
        public GUIFactory()
        {
        }
        public GUIFactory(UndoSystem undoSystem) : base(undoSystem)
        {
        }

        /// <summary>
        /// Create a button that can ping Asset.
        /// </summary>
        public virtual Button CreatePingButton(string pathRelativeProject)
        {
            return CreateButton(PackageAssets.Icons.jump, 16f, () => EditorGUIUtility.PingObject(AssetDatabase.LoadAssetAtPath<Object>(pathRelativeProject)));
        }

        /// <summary>
        /// Create a <see cref="FolderPicker"/> Control.
        /// </summary>
        public virtual FolderPicker CreateFolderPicker()
        {
            return new FolderPicker(this);
        }
        public FolderPicker CreateFolderPicker(string label)
        {
            FolderPicker folderPicker = CreateFolderPicker();
            folderPicker.label = label;
            return folderPicker;
        }
        public FolderPicker CreateFolderPicker(string label, string panelTitle)
        {
            FolderPicker folderPicker = CreateFolderPicker(label);
            folderPicker.panelTitle = panelTitle;
            return folderPicker;
        }
        public FolderPicker CreateFolderPicker(string label, string panelTitle, Action<string> onValueChangedCallback)
        {
            FolderPicker folderPicker = CreateFolderPicker(label, panelTitle);
            folderPicker.onValueChanged += onValueChangedCallback;
            return folderPicker;
        }
        public FolderPicker CreateFolderPicker(string label, string panelTitle, string defaultValue)
        {
            FolderPicker folderPicker = CreateFolderPicker(label, panelTitle);
            folderPicker.SetValueWithoutNotify(defaultValue);
            return folderPicker;
        }
        public FolderPicker CreateFolderPicker(string label, string panelTitle, string defaultValue, Action<string> onValueChangedCallback)
        {
            FolderPicker folderPicker = CreateFolderPicker(label, panelTitle, defaultValue);
            folderPicker.onValueChanged += onValueChangedCallback;
            return folderPicker;
        }

        /// <summary>
        /// Create a <see cref="CreateBar"/> Control.
        /// </summary>
        public virtual CreateBar CreateCreateBar()
        {
            return new CreateBar(this);
        }
        public CreateBar CreateCreateBar(string label)
        {
            CreateBar createBar = CreateCreateBar();
            createBar.label = label;
            return createBar;
        }
        public CreateBar CreateCreateBar(Action<string> onConfirmCallback, Action onCancelCallback)
        {
            CreateBar createBar = CreateCreateBar();
            createBar.onConfirm += onConfirmCallback;
            createBar.onCancel += onCancelCallback;
            return createBar;
        }
        public CreateBar CreateCreateBar(string label, Action<string> onConfirmCallback, Action onCancelCallback)
        {
            CreateBar createBar = CreateCreateBar(onConfirmCallback, onCancelCallback);
            createBar.label = label;
            return createBar;
        }

        public virtual ObjectEditorControl CreateObjectEditorControl()
        {
            return new ObjectEditorControl(this);
        }
        public ObjectEditorControl CreateObjectEditorControl(string objectName)
        {
            ObjectEditorControl objectEditorControl = CreateObjectEditorControl();
            objectEditorControl.SetObjectName(objectName);
            return objectEditorControl;
        }

        public virtual Panel CreatePanel()
        {
            return new Panel();
        }
        public Panel CreatePanel(VisualElement child)
        {
            Panel panel = CreatePanel();
            panel.Add(child);
            return panel;
        }
        public Panel CreatePanel(string title)
        {
            Panel panel = CreatePanel();
            panel.title = title;
            return panel;
        }
        public Panel CreatePanel(string title, TextAnchor titleAnchor)
        {
            Panel panel = CreatePanel(title);
            panel.titleAnchor = titleAnchor;
            return panel;
        }
        public Panel CreatePanel(string title, VisualElement child)
        {
            Panel panel = CreatePanel(title);
            panel.Add(child);
            return panel;
        }
        public Panel CreatePanel(string title, TextAnchor titleAnchor, VisualElement child)
        {
            Panel panel = CreatePanel(title, titleAnchor);
            panel.Add(child);
            return panel;
        }
    }
}